Responsive images
一个改进就是展示裁切(cropped)版本的图像。 either all showing the same thing but containing different numbers of pixels (resolution switching), or different images suitable for different space allocations (art direction).
Create responsive images
Different sizes
srcset
and sizes
<img
srcset="elva-fairy-480w.jpg 480w, elva-fairy-800w.jpg 800w"
sizes="(max-width: 600px) 480px,
800px"
src="elva-fairy-800w.jpg"
alt="Elva dressed as a fairy" />
srcset
定义了让浏览器选择的图像,和各个图像的大小是什么样的。
For each one, we write:
- An image filename (
elva-fairy-480w.jpg
) - A space
- The image's intrinsic width in pixels (
480w
) — note that this uses thew
unit, notpx
as you might expect. An image's intrinsic size is its real size, which can be found by inspecting the image file on your computer (for example, on a Mac you can select the image in Finder and press Cmd + I to bring up the info screen).
sizes
defines a set of media conditions(e.g. screen widths)
- A media condition (
max-width:600px
),一个媒体情况描述了一个屏幕可能的情况。 - A space
- The width of the slot the image will fill when the media condition is true (480px)
Note:对于slot width,给一个绝对宽度(480px)不如给一个相对的viewport(50vw)vw:viewport width.最后一个slot width没有media condition(这是默认选择,当没有media conditions是true的时候)。当浏览器第一次选择时,会忽视之后的所有选择。
浏览器会怎么做呢:
- 查询设备宽度。
- 看看
sizes
里哪个is true。 - 查看给media query的slot大小。
- 加载
srcset
里的。
老的浏览器会直接加载src
里的图片。
Note:在<head>
里,你会发现<meta name="viewport" content= "width=device-width">
强迫手机浏览器给出真实的viewport。
Same size ,different resolutions
只写srcset
和1.5x-descriptors(描述符),不写sizes
<img
srcset="elva-fairy-320w.jpg, elva-fairy-480w.jpg 1.5x, elva-fairy-640w.jpg 2x"
src="elva-fairy-640w.jpg"
alt="Elva dressed as a fairy" />
CSS:
img {
width: 320px;
}
CSS pixels
如果屏幕是1 CSS pixel就加载320w。如果是每CSS像素有两个device pixels。就加载640w。
Art direction
<picture>
就像<video>
和<audio>
一样,是一个wrapper
<picture>
<source media= "(max-width:799px)" srcset= "elva-480w-close-portrait.jpg" />
<source media= "(min-width:800px)" srcset= "elva-800w.jpg" />
<img src="elva-800w.jpg" alt= "Chris standing up holding his daughter Elva" />
</picture>
- 如果小于799px就第一个,如果800px就第二个。
- 就像
size
那样<source>
能有很多srcset
- 但是你必须在
</picture>
之前加一个<img>
标签,里面有src
和alt
,不然会没图片。如果前面的source
没有ture的就用这个,有的浏览器啥都不支持。
Note:你只应该在ART DIRECTION这个情景中用media
属性,如果你用了media
,就不要在sizes
属性里再添加media conditions了。
为什么不用CSS或者Javascript
浏览器开始加载页面时,会在主解析器开始加载和解析CSS和js之前开始下载,但是对响应式图片没有帮助,所以有srcset
的方法。因为你不能先加载好 <img>
元素后,再用 JavaScript 检测可视窗口的宽度,如果觉得大小不合适,再动态地加载小的图片替换已经加载好的图片,这样的话,原始的图像已经被加载了,然后你又加载了小的图像,这反而更不“响应”了。
大胆的使用现代图像格式
像 WebP 和 AVIF 等新型图片格式可以做到高质量的同时保持较低的文件大小,如今这些格式已有相对广泛的浏览器支持,且几乎没有“历史包袱”。
<picture>
让我们能继续满足老式浏览器的需要。你可以在 type
属性中提供 MIME 类型,这样浏览器就能立即拒绝其不支持的文件类型:
HTMLCopy to Clipboard
<picture>
<source type="image/svg+xml" srcset="pyramid.svg" />
<source type="image/webp" srcset="pyramid.webp" />
<img
src="pyramid.png"
alt="regular pyramid built from four equilateral triangles" />
</picture>
- 不要使用
media
属性,除非你也需要用到美术设计。 - 在
<source>
元素中,你只可以引用在type
中声明的文件类型。 - 像之前一样,如果必要,你可以在
srcset
和sizes
中使用逗号分割的列表。